﻿using e_commerce.BLL.Data;
using e_commerce.BLL.Models;
using System;
using System.Collections.Generic;
using System.Linq;
using System.Text;
using System.Threading.Tasks;

namespace e_commerce.BLL.Services.Enterprise
{
    public class OrderService : IOrderEnterpriseManager, IDisposable
    {
        private commerceDbContext _dbContext;
        private GoodsManager _gManager;
        public OrderService()
        {
            _dbContext = new commerceDbContext();
            _gManager = new GoodsManager();
        }

        private Order GetOrderById(string orderId)
        {
            var order = _dbContext.Order.SingleOrDefault(o => o.OrderId == orderId && !o.IsDelete);
            if (order == null)
            {
                throw new Exception("未查询到订单信息");
            }
            return order;
        }

        public void AcceptOrderByOrderId(string orderId)
        {

            var order = GetOrderById(orderId);  //获取订单
            order.State = (int)OrderState.Noreceived;  //改变订单状态  
            var goods = _gManager.GetGoodsById(order.GoodsId);   //获取商品
            goods.Deal += order.Count;  //增加商品销售量
            OperateGoodsStock(order.GoodsId, 1, order.Count);  //操作库存
            SaveChange();


        }
        /// <summary>
        /// 修改商品库存
        /// </summary>
        /// <param name="goodsId">商品id</param>
        /// <param name="operate">操作类型1库存减 2库存加 3库存清零</param>
        /// <param name="count">库存操作量</param>
        private void OperateGoodsStock(int goodsId, int operate, int count)
        {
            var goods = _gManager.GetGoodsById(goodsId);
            switch (operate)
            {
                case 1: goods.Stock -= count; break;
                case 2: goods.Stock += count; break;
                case 3: goods.Stock = 0; break;
            }
        }

        public IEnumerable<Order> GetNewOrders(int count)
        {
            return _dbContext.Order.OrderByDescending(o => o.CreateTime).Where(o => o.State == (int)OrderState.Untreated).Take(count);
        }
        public IEnumerable<Order> GetAllOrderByPage(int state, int page, int pageSize, ref int totalCount)
        {
            IEnumerable<Order> order;
            if (state == 0)
            {
                order = _dbContext.Order.OrderByDescending(m => m.CreateTime).Where(o => !o.IsDelete)
                .Skip((page - 1) * pageSize)
                .Take(pageSize);
                totalCount = _dbContext.Order.Count();
            }
            else
            {
                order = _dbContext.Order.OrderBy(m => m.CreateTime)
                    .Where(o => o.State == state && !o.IsDelete)
                    .Skip((page - 1) * pageSize)
                    .Take(pageSize);
                totalCount = _dbContext.Order.Where(o => o.State == state).Count();
            }
            return order;
        }

        public string GetOrderState(OrderState state)
        {
            string result = string.Empty;
            switch (state)
            {
                case OrderState.Unpaid: result = "待付款"; break;
                case OrderState.Untreated: result = "未处理"; break;
                case OrderState.Noship: result = "未发货"; break;
                case OrderState.Noreceived: result = "未收货"; break;
                case OrderState.OrderOver: result = "订单已完成"; break;
                case OrderState.ApplyRefund: result = "申请退款中"; break;
                case OrderState.OnRefund: result = "已退款"; break;
                case OrderState.ApplyReturn: result = "申请退货"; break;
                case OrderState.OnReturn: result = "已退货"; break;
                case OrderState.CanselOrder: result = "订单已取消"; break;
                default: result = "订单状态异常"; break;
            }
            return result;
        }

        public IEnumerable<Order> GetRecycleOrders(int page, int pageSize, ref int totalCount)
        {
            var order = _dbContext.Order.OrderBy(m => m.CreateTime).Where(o => o.IsDelete)
                    .Skip((page - 1) * pageSize)
                    .Take(pageSize);
            totalCount = _dbContext.Order.Where(o => o.IsDelete).Count();
            return order;
        }
        public void AgreeRefundByOrderId(string orderId)
        {
            var order = GetOrderById(orderId);
            //
        }

        /// <summary>
        /// 同意退款
        /// </summary>
        /// <param name="orderId"></param>
        public void AgreeReturnByOrderId(string orderId)
        {
            throw new NotImplementedException();
        }

        /// <summary>
        /// 确认收货
        /// </summary>
        /// <param name="orderId"></param>
        public void ConfirmDeliverByOrderId(string orderId)
        {
            var order = GetOrderById(orderId);
            order.State = (int)OrderState.OrderOver;
        }

        public void Dispose()
        {
            _dbContext.Dispose();
        }

        public IEnumerable<Refund> GetRefundByPage(int page, int size)
        {
            var refunds = (from r in _dbContext.Refund
                           orderby r.CreateTime
                           select r).Skip((page - 1) * size).Take(size);
            return refunds;
        }
        public void ModifyRemarkByOrderId(string orderId, string remark)
        {
            var order = GetOrderById(orderId);
            order.OrderRemark = remark;
            SaveChange();
        }

        /// <summary>
        /// 拒绝退款
        /// </summary>
        /// <param name="orderId"></param>
        public void RefuseRefundByOrderId(string orderId)
        {
            throw new NotImplementedException();
        }

        /// <summary>
        /// 拒绝退货
        /// </summary>
        /// <param name="orderId"></param>
        public void RefuseReturnByOrderId(string orderId)
        {
            throw new NotImplementedException();
        }

        private void SaveChange()
        {
            _dbContext.SaveChanges();
        }
        

        public IEnumerable<Refund> GetNewRefund(int count)
        {
            return _dbContext.Refund.OrderByDescending(r => r.CreateTime).Take(count);
        }
    }
}
